package com.molichuxing.services.infrastructure.service;

import com.molichuxing.framework.dto.Paged;
import com.molichuxing.framework.dto.TabDto;
import com.molichuxing.framework.service.RootService;
import com.molichuxing.services.business.dto.response.GoodsSalesStatisticsBizDto;
import com.molichuxing.services.business.dto.response.OrderCarInfoAppDto;
import com.molichuxing.services.infrastructure.dto.request.create.OrderSubscribeCreateDto;
import com.molichuxing.services.infrastructure.dto.request.modify.*;
import com.molichuxing.services.infrastructure.dto.response.OrderSubscribeDto;
import com.molichuxing.services.property.OrderListTypeEnum;
import com.molichuxing.services.property.OrderSubscribeStatusEnum;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Map;

/**
 * 订阅里程订单基础服务
 *
 * @author zoumingyu
 * @date 2019年8月13日
 */
public interface OrderSubscribeService extends RootService {

    /**
     * 订阅里程订单信息
     *
     * @param orderCode 订单号
     * @return
     */
    public OrderSubscribeDto getOrderSubscribe(Long orderCode);

    /**
     * 查询订阅订单信息
     *
     * @param parentOrderCode      父订单号
     * @param orderSubscribeStatus 订单状态
     * @return
     */
    public OrderSubscribeDto getOrderSubscribeByParent(Long parentOrderCode,
                                                       OrderSubscribeStatusEnum orderSubscribeStatus);

    /**
     * 分页获取订阅里程订单信息
     *
     * @param params   listType：列表类型-enum <br />
     *                 orderStatus：订单状态-enum <br />
     *                 orderCode：订单号-long <br />
     *                 userIds：用户id-list <br />
     *                 storeIds：门店id-list <br />
     *                 orderTimeStart：下单开始时间-LocalDate <br />
     *                 orderTimeEnd：下单结束时间-LocalDate <br />
     *                 isHaveSuborder：有无续订-boolean
     * @param pageNum  页数
     * @param pageSize 每页条数
     * @return
     * @throws Exception
     */
    public Paged<OrderSubscribeDto> getOrderList(Map<String, Object> params, int pageNum, int pageSize)
            throws Exception;

    /**
     * 根据用户id查询订阅里程订单信息
     *
     * @param userId 用户id
     * @return
     */
    public List<OrderSubscribeDto> getOrderListByUser(Integer userId);

    /**
     * 根据用户id查询有效订单（未取消、未删除）
     *
     * @param userId 用户id
     * @return
     */
    public List<OrderSubscribeDto> getNormalByUser(Integer userId);

    /**
     * 根据车辆id查询订阅里程订单信息
     *
     * @param carId 车辆id
     * @return
     */
    public List<OrderSubscribeDto> getOrderListByCar(Integer carId);

    /**
     * 根据车辆id查询订阅里程订单信息
     *
     * @param carId    车辆id
     * @param storeIds 门店ids
     * @return
     */
    public List<OrderSubscribeDto> getOrderListByCar(Integer carId, List<Integer> storeIds);

    /**
     * 统计每种状态下的数据量
     *
     * @param orderListType 列表类型枚举
     * @return
     */
    public List<TabDto> getStatusStatistics(OrderListTypeEnum orderListType);

    /**
     * 统计每种状态下的数据量
     *
     * @param orderListType 列表类型枚举
     * @param storeIds      门店ids
     * @return
     */
    public List<TabDto> getStatusStatistics(OrderListTypeEnum orderListType, List<Integer> storeIds);

    /**
     * 根据用户id查询订单号
     *
     * @param userId 用户id
     * @return
     */
    public List<Long> getOrderCodeByUser(Integer userId);

    /**
     * 根据用户id查询订单号
     *
     * @param userIds 用户id
     * @return
     */
    public List<Long> getOrderCodeByUser(List<Integer> userIds);

    /**
     * 根据用户查询用车中的车辆id
     *
     * @param userId
     * @return
     */
    public List<OrderCarInfoAppDto> getUseCarIdByUser(Integer userId, Integer orderStatus);

    /**
     * 新增订阅里程订单
     *
     * @param createDto
     * @return id
     */
    public Integer create(OrderSubscribeCreateDto createDto);

    /**
     * 订单状态修改
     *
     * @param orderCode      订单号
     * @param preOrderStatus 修改前状态
     * @param orderStatus    修改后状态
     * @return
     */
    public Boolean modify(Long orderCode, OrderSubscribeStatusEnum preOrderStatus,
                          OrderSubscribeStatusEnum orderStatus);

    /**
     * 支付完成修改订阅订单
     *
     * @param modifyDto
     * @return
     */
    public Boolean modifyPay(OrderPayModifyDto modifyDto);

    /**
     * 续订完成修改订单信息（是否有续订单改为有）
     *
     * @param orderCode 订单号
     * @return
     */
    public Boolean modifyRenew(Long orderCode);

    /**
     * 统计排序订单商品销量
     *
     * @return
     */
    public List<Map<String, Object>> getStatisticsGoods();

    /**
     * 提车完成修改订阅订单
     *
     * @param modifyDto
     * @return
     */
    public Boolean modifyDelivery(OrderDeliveryModifyDto modifyDto);

    /**
     * 加购成功后修改订单预警里程
     *
     * @param orderCode       订单号
     * @param totalPayMileage 添加里程数
     * @return
     */
    public Boolean modifyWarningMileageByPurchase(Long orderCode, Integer totalPayMileage);

    /**
     * 查询订阅里程订单待审核数量
     *
     * @return
     */
    public Integer getOrderSubscribePendCount();

    /**
     * 获取有效订阅续订订单信息（已支付）
     *
     * @param parentOrderCode 父订单号
     * @return
     */
    public OrderSubscribeDto getEffectiveOrderSubscribeByParent(Long parentOrderCode);

    /**
     * 订阅超时未还车数量
     */
    public Integer getSubscribeOvertimeCount();

    /**
     * 获取截止日未还车订单
     *
     * @param leaseExpire
     * @return
     */
    public List<OrderSubscribeDto> getOrderExpire(LocalDate leaseExpire);

    /**
     * 订单结束时修改订阅订单
     *
     * @param modifyDto
     * @param oldStatus
     * @return
     */
    public boolean modifyFinish(OrderFinishModifyDto modifyDto, OrderSubscribeStatusEnum oldStatus);

    /**
     * 订单用车中修改
     *
     * @param modify
     * @return
     */
    public boolean modifyUse(OrderUseModifyDto modifyDto);

    /**
     * 订单租期结束修改结束里程
     *
     * @param orderCode  订单号
     * @param endMileage 结束时里程
     * @return
     */
    public boolean modifyEndMileageByExpire(Long orderCode, Integer endMileage);


    /**
     * 查询最近N天，每天的订阅数量
     *
     * @param days
     * @return
     */
    public Map<String, Integer> getSubscribeCountByDay(Integer days);


    /**
     * 查询N天前的订阅订单数量
     *
     * @return
     */
    public Integer getSubscribeYesterdayCount(Integer days);


    /**
     * 查询订阅订单中所有用车中的
     *
     * @return
     */
    public List<OrderSubscribeDto> getSubscribeTradeUse();

    /**
     * 查询订阅订单信息
     *
     * @param payDate     支付日期
     * @param orderStatus 订单状态
     * @return
     */
    public List<OrderSubscribeDto> getSubscribe(LocalDate payDate, OrderSubscribeStatusEnum orderStatus);

    /**
     * 查询不存在续订单的订阅订单
     *
     * @param leaseExpire
     * @param orderStatus
     * @return
     */
    public List<OrderSubscribeDto> getNoneRenewable(LocalDate leaseExpire, OrderSubscribeStatusEnum orderStatus);

    /**
     * 订单还车修改订单
     *
     * @param modifyDto
     * @return
     */
    public Boolean modifyReturnCar(OrderReturnCarModifyDto modifyDto);


    /**
     * 查询当天支付成功的
     *
     * @return
     */
    public List<LocalDateTime> getTodaySubscribeCount();

    /**
     * 查询已提车的订阅订单（包含已支付续订单）
     *
     * @return
     */
    public Map<Integer, Integer> getEffectiveOrderVehicleStatistics();

    /**
     * 查询每个门店下生效订单（提车、续订生效）数量
     *
     * @return
     */
    Map<Integer, Integer> getEffectiveOrderStoreStatistics();

    /**
     * 查询统计每种商品已支付的订阅订单
     *
     * @return
     */
    List<GoodsSalesStatisticsBizDto> getEffectiveOrderGoodsStatistics();
}
